package com.shijunhao.graduation.service.system.impl;

import cn.hutool.core.date.DatePattern;
import cn.hutool.core.util.IdUtil;
import com.shijunhao.graduation.domain.entity.SystemFileInfo;
import com.shijunhao.graduation.exception.BusinessException;
import com.shijunhao.graduation.exception.SystemRuntimeException;
import com.shijunhao.graduation.mapper.SystemFileInfoMapper;
import com.shijunhao.graduation.service.system.ISystemFileInfoService;
import com.shijunhao.graduation.utils.ServletUtils;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.ContentDisposition;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.Date;
import java.util.Objects;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author shijunhao
 * @since 2022-03-07
 */
@Service
public class SystemFileInfoServiceImpl extends BaseServiceImpl<SystemFileInfoMapper, SystemFileInfo> implements ISystemFileInfoService {

    @Value("${graduation.file-path}")
    private String localPath;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public SystemFileInfo upload(MultipartFile file) {
        SystemFileInfo fileInfo = new SystemFileInfo();

        //设置文件名及格式大小
        fileInfo.setFileName(StringUtils.defaultIfBlank(file.getOriginalFilename(), file.getName()));
        fileInfo.setFormat(StringUtils.defaultIfBlank(fileInfo.getFileName().substring(fileInfo.getFileName().lastIndexOf('.')), "null"));
        fileInfo.setSize(file.getSize());
        //设置随机文件名
        String randomName = IdUtil.fastUUID() + fileInfo.getFormat();
        fileInfo.setRandomName(randomName);
        //设置文件路径，相对【yyyyMMdd/randomName】
        String time = DatePattern.PURE_DATE_FORMAT.format(new Date());
        String filePath = time + "/" + randomName;
        fileInfo.setFilePath(filePath);
        super.insertOne(fileInfo);

        InputStream inputStream = null;
        OutputStream outputStream = null;
        try {
            inputStream = IOUtils.buffer(file.getInputStream());
            File localFile = new File(localPath + filePath);
            outputStream = IOUtils.buffer(FileUtils.openOutputStream(localFile));
            IOUtils.copy(inputStream, outputStream);
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                if (outputStream != null)
                    outputStream.close();
                if (inputStream != null)
                    inputStream.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return fileInfo;
    }

    @Override
    public void download(Long fileId) {
        SystemFileInfo fileInfo = super.getById(fileId);
        if (fileInfo == null)
            throw new BusinessException("文件信息不存在！");
        File file = new File(localPath + fileInfo.getFilePath());
        HttpServletResponse response = ServletUtils.getResponse();
        if(response == null)
            throw new SystemRuntimeException("系统异常!");
        if (!file.exists()){
            throw new BusinessException("文件信息不存在！");
        }else{
            FileInputStream inputStream = null;
            BufferedOutputStream buffer = null;
            try {
                inputStream = FileUtils.openInputStream(file);
                buffer = IOUtils.buffer( response.getOutputStream());
                response.setStatus(200);
                response.setCharacterEncoding(StandardCharsets.UTF_8.name());
                response.setHeader("Content-Disposition", ContentDisposition.builder("form-data")
                        .name("attachment")
                        .filename(fileInfo.getFileName(), StandardCharsets.UTF_8)
                        .build().toString());
                IOUtils.copy(inputStream, buffer);
                buffer.flush();
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                try {
                    if(inputStream != null)
                        inputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }


    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public SystemFileInfo upload(String content) {
        SystemFileInfo fileInfo = new SystemFileInfo();
        fileInfo.setFormat(".txt");
        String randomName = IdUtil.fastUUID() + fileInfo.getFormat();
        fileInfo.setFileName(randomName);
        fileInfo.setRandomName(randomName);
        //设置文件路径，相对【yyyyMMdd/randomName】
        String time = DatePattern.PURE_DATE_FORMAT.format(new Date());
        String filePath = time + "/" + randomName;
        fileInfo.setFilePath(filePath);
        File file = new File(localPath+filePath);
        try {
            FileUtils.write(file,content, StandardCharsets.UTF_8);
        } catch (IOException e) {
            throw new SystemRuntimeException("系统异常!");
        }

        fileInfo.setSize(file.length());
        super.insertOne(fileInfo);
        return fileInfo;
    }

    @Override
    public File getFile(Long id) {
        SystemFileInfo info = getById(id);
        if(info == null){
            throw new SystemRuntimeException("文件信息不存在!");
        }
        return new File(localPath+info.getFilePath());
    }
}
